package benchmarks;

import java.util.ArrayList;
import java.util.List;

public enum Mode {


    Throughput("thrpt", "Throughput, ops/time"),


    AverageTime("avgt", "Average time, time/op"),


    SampleTime("sample", "Sampling time"),

    SingleShotTime("ss", "Single shot invocation time"),

    /**
     * Meta-mode: all the benchmark modes. This is mostly useful for internal JMH testing.
     */
    All("all", "All benchmark modes"),

    ;

    private final String shortLabel;
    private final String longLabel;

    Mode(String shortLabel, String longLabel) {
        this.shortLabel = shortLabel;
        this.longLabel = longLabel;
    }

    public String shortLabel() {
        return shortLabel;
    }

    public String longLabel() {
        return longLabel;
    }

    public static Mode deepValueOf(String name) {
        try {
            return Mode.valueOf(name);
        } catch (IllegalArgumentException iae) {
            Mode inferred = null;
            for (Mode type : values()) {
                if (type.shortLabel().startsWith(name)) {
                    if (inferred == null) {
                        inferred = type;
                    } else {
                        throw new IllegalStateException("Unable to parse benchmark mode, ambiguous prefix given: \"" + name + "\"\n" +
                            "Known values are " + getKnown());
                    }
                }
            }
            if (inferred != null) {
                return inferred;
            } else {
                throw new IllegalStateException("Unable to parse benchmark mode: \"" + name + "\"\n" +
                    "Known values are " + getKnown());
            }
        }
    }

    public static List<String> getKnown() {
        List<String> res = new ArrayList<>();
        for (Mode type : Mode.values()) {
            res.add(type.name() + "/" + type.shortLabel());
        }
        return res;
    }


    public static void main(String[] args) {
        Mode m = Mode.valueOf(Mode.Throughput.toString());
        System.out.println(Mode.Throughput.ordinal());
        System.out.println(Mode.AverageTime.ordinal());
        System.out.println(Mode.SingleShotTime.ordinal());
        System.out.println(m.longLabel());
        System.out.println(m.shortLabel());
    }

}
